package comm

import (
	"poker/pb/proto/assets"
	"poker/pb/proto/common"
	"poker/pb/proto/tablerecord"

	"go.mongodb.org/mongo-driver/bson/primitive"
)

const (
	Login_Guest             = 1 // 来宾登录
	Login_Mobile            = 2 // 手机登录
	Login_Account           = 3 // 账号登录
	Login_Token             = 4 // TOKEN登录
	Login_WechatNative      = 5 // 微信原生登录
	Login_WechatMini        = 6 // 小游戏登录
	Login_OneClick          = 7 // 一键登录
	Login_Coin_Channel_FP   = 8 // 方片游戏渠道登录
	Login_Coin_Channel_ZHQP = 9 //中华壳牌
)

type ItemTy int32

const (
	ITEM_TY_COMMON    ItemTy = 1 // 普通道具
	ITEM_TY_ENTITY    ItemTy = 2 // 实物
	ITEM_TY_TICKET    ItemTy = 3 // 优惠券
	ITEM_TY_CHIP      ItemTy = 4 // 碎片
	ITEM_TY_VIP       ItemTy = 5 // VIP
	ITEM_TY_REDPECKET ItemTy = 6 // 红包

	ITEM_TY_CURRENCY ItemTy = 999 // 货币类型
)

type Item struct {
	ID    int32   `json:"id" bson:"id"`
	Count float64 `json:"count" bson:"count"`
}

type Cash struct {
	Name  string  `json:"name" bson:"name"`
	Count float64 `json:"count" bson:"count"`
}

type Special struct {
	Key     string `bson:"key" json:"key"`
	Rewards []Item `bson:"rewards" json:"rewards"`
}

type RedPacket struct {
	UID    int64
	Count  float64
	Memo   string
	Reason assets.ChangeType
}

type MatchTable struct {
	ID        int32 // 本地桌号
	Players   []int64
	StartTime int64 // 桌子开始时间
	EndTime   int64 // 桌子结束时间
}

type TeamRank struct {
	Uid1       int64     `json:"uid1"`
	Uid2       int64     `json:"uid2"`
	Scores     []float64 `json:"scores"`
	ScoreNames []string  `json:"scoreNames"`
	ScoreKeys  []string  `json:"scoreKeys"`
}

type MatchRank struct {
	UID   int64
	Score int64
}

type Act7SignData struct {
	Received [7]int32 `json:"received" bson:"received"`
	Special  []string `json:"login" bson:"login"` // 标记领取的第几天
}

type ActLoginData struct {
	Received []string `json:"received" bson:"received"` // 领取日期
}

type ActGivingData struct {
	Received []string `json:"received" bson:"received"` // 次数
}

type Act3DayData struct {
	Stair    int32               `bson:"stair" json:"stair"` // 当前阶段
	Day      int32               `bson:"day" json:"day"`
	Date     *primitive.DateTime `bson:"timestamp" json:"timestamp"` // 上次充值时间
	Point    int32               `bson:"point" json:"point"`
	Received map[string]int32    `bson:"received" json:"received"` // 领取阶段记录 0 为领取 1可领取 2已领取
	Time     primitive.DateTime  `bson:"time" json:"time"`         // 上次检查时间
}

type ActTurntableData struct {
	Times    int32 `bson:"times" json:"times"` // 今日已参与次数
	LastTime int64 `bson:"last_time" json:"last_time"`
	NextTime int64 `bson:"next_time" json:"next_time"` // 下次参与时间
}

type ActWeeklyTreasureData struct {
	Received []string `bson:"received" json:"received"`
	Special  []string `bson:"special" json:"special"` // 特殊奖励
	Points   int32    `bson:"points" json:"points"`
	Tasks    []int32  `bson:"tasks" json:"tasks"` // 当前的任务id
}

type ActRedPackData struct {
	Received []string `bson:"received" json:"received"`
	Special  []string `bson:"special" json:"special"` // 特殊奖励
	Points   int32    `bson:"points" json:"points"`
	Tasks    []int32  `bson:"tasks" json:"tasks"` // 当前的任务id
}

type ActYbwlData struct {
	Received int32   `bson:"received" json:"received"` // 0 不可领取 1可领取 2 已领取
	IsOpen   int32   `bson:"is_open" json:"is_open"`
	Tasks    []int32 `bson:"tasks" json:"tasks"` // 当前的任务id
}

type Friend struct {
	UID      int64  `bson:"uid" json:"uid"`
	Nickname string `bson:"nickname" json:"nickname"`
	Avatar   string `bson:"avatar" json:"avatar"`
	Level    int32  `bson:"level" json:"level"`
	VipLevel int32  `bson:"vip_level" json:"vip_level"`
	State    int32  `bson:"state" json:"state"`
}

type SimpleUser struct {
	UID      int64  `bson:"uid" json:"uid"`
	Nickname string `bson:"nickname" json:"nickname"`
	Avatar   string `bson:"avatar" json:"avatar"`
	Level    int32  `bson:"level" json:"level"`
	VipLevel int32  `bson:"vip_level" json:"vip_level"`
	State    int32  `bson:"state" json:"state"`
}

type Address struct {
	Name   string `bson:"name" json:"name"`
	Phone  string `bson:"phone" json:"phone"`
	Detail string `bson:"detail" json:"detail"` // 详情
}

type AddrList struct {
	DefIndex int32      `bson:"def_index" json:"def_index"`
	List     []*Address `bson:"list" json:"list"`
}

type Rank struct {
	UID       int64   `bson:"uid" json:"uid"`
	Nickname  string  `bson:"nickname" json:"nickname"`
	Avatar    string  `bson:"avatar" json:"avatar"`
	Mobile    string  `bson:"mobile" json:"mobile"`
	Max       int32   `bson:"max" json:"max"`
	Score     float64 `bson:"score" json:"score"`
	UpScore   float64 `bson:"up_score" json:"up_score"`   // 去首累进分
	LvDiff    int64   `bson:"lv_diff" json:"lv_diff"`     // 级差分
	LvCount   int64   `bson:"lv_count" json:"lv_count"`   // 升级数
	WinCount  int64   `bson:"win_count" json:"win_count"` // 胜场
	Partner   int64   `bson:"partner" json:"partner"`     // 搭档分
	Total     float64 `bson:"total" json:"total"`
	HideScore float64 `bson:"hide_score" json:"hide_score"` // 隐藏分 用于排序
	LastScore float64 `bson:"last_score" json:"last_score"` // 上一轮的隐藏分
	LastRank  int32   `bson:"last_rank" json:"last_rank"`   // 上一轮排名
	Reward    bool    `bson:"reward" json:"reward"`
	Escape    bool    `bson:"escape" json:"escape"`     // 逃跑
	Round     int32   `bson:"round" json:"round"`       // 用户打到第几轮了
	InTable   bool    `bson:"in_table" json:"in_table"` // 是否在桌内逃跑
	SignT     int64   `bson:"sign_t" json:"sign_t"`     // 最近确认时间
	ScoreBase float64 `bson:"score_base" json:"score_base"`
}
type DragIn struct {
	ItemId       int32
	Count        float64
	ServerCharge float64
}

type Strategy struct {
	Limit int64 `bson:"limit" json:"limit"`
	Count int64 `bson:"count" json:"count"` // 本次获得的金币数
}

type TableUser struct {
	UID              int64               `bson:"uid" json:"uid"`           // 用户ID
	Nickname         string              `bson:"nickname" json:"nickname"` // 用户昵称
	Nicknameh        string              `bson:"nicknameh" json:"nicknameh"`
	RealName         string              `bson:"real_name" json:"real_name"` // 用户姓名
	Avatar           string              `bson:"avatar" json:"avatar"`       // 用户头像
	Signature        string              `bson:"signature" json:"signature"` // 用户签名
	Gender           common.Gender       `bson:"gender" json:"gender"`       // 用户性别
	Level            int32               `json:"level"`                      // 用户等级
	Currency         []*common.Item      `bson:"currency" json:"currency"`
	IsRobot          bool                `bson:"isRobot" json:"isRobot"`
	Vip              *common.Vip         `bson:"vip" json:"vip"`
	WinRate          []*common.WinRate   `bson:"winRate" json:"win_rate"`
	ActiveScore      float32             `bson:"active_score" json:"active_score"`             // 活跃度年度积分
	MasterPointScore float32             `bson:"master_point_score" json:"master_point_score"` // 大师分年度积分
	GetLikes         int64               `bson:"get_likes" json:"get_likes"`                   // 获得到的点赞数
	DragGold         *DragIn             `bson:"drag_gold" json:"drag_gold"`
	IsRobotSE        bool                `bson:"is_robot_se" json:"is_robot_se"`
	NoviceStrategy   int32               `bson:"novice_strategy" json:"novice_strategy"`       // 新手策略
	Strategy         Strategy            `bson:"strategy" json:"strategy"`                     // 策略限额
	LastRechargeDate *primitive.DateTime `bson:"last_recharge_date" json:"last_recharge_date"` // 上次充值日期
	RealFlag         int32               `bson:"real_flag" json:"real_flag"`
}

func (u *TableUser) CountCurrencyById(currencyId int32) float64 {
	var count float64

	for _, v := range u.Currency {
		if v.Id == currencyId {
			count = v.Count
			break
		}
	}
	return count
}

func (u *TableUser) CountGameTimes(ty int32) int32 {
	var count int32
	for _, v := range u.WinRate {
		if v.Game == ty || ty == 0 {
			count += v.Win
			count += v.Lose
			count += v.Escape
		}
	}
	return count
}

func (u *TableUser) ToPb() *common.TableUser {
	res := &common.TableUser{
		UID:       u.UID,
		Nickname:  u.Nickname,
		Avatar:    u.Avatar,
		Signature: u.Signature,
		Gender:    u.Gender,
		Currency:  u.Currency,
		//Vip:              u.Vip,
		GetLikes:         u.GetLikes,
		WinRate:          u.WinRate,
		ActiveScore:      u.ActiveScore,
		MasterPointScore: u.MasterPointScore,
		Nicknameh:        u.Nicknameh,
		RealName:         u.RealName,
	}
	res.Vip = new(common.Vip)
	res.Vip.Level = u.Vip.Level
	if u.DragGold != nil {
		res.DragGold = &common.DragGold{}
		res.DragGold.ItemId = u.DragGold.ItemId
		res.DragGold.ServerCharge = u.DragGold.ServerCharge
		res.DragGold.Count = u.DragGold.Count
	}

	return res
}

type TableInfoSamplePlayer struct {
	User    *TableUser `bson:"user" json:"user"`
	IsReady bool       `bson:"is_ready" json:"is_ready"`
}

// 桌子的简略信息 存储在redis
type TableInfoSample struct {
	ServerID     string                           `bson:"server_id" json:"server_id"`
	Id           int64                            `bson:"game_id" json:"game_id"`    //游戏唯一id
	CurScore     []int32                          `bson:"cur_score" json:"curScore"` //当前分数
	Players      map[int32]*TableInfoSamplePlayer `bson:"players" json:"players"`    //0,2攻  1,3守
	State        int32                            `bson:"state" json:"state"`        //桌子状态
	GamePlayType common.GamePlayType              `bson:"game_play_type" json:"game_play_type"`
}

func (t *TableInfoSample) ToPb() *tablerecord.TableInfoSample {
	res := &tablerecord.TableInfoSample{
		Id:           t.Id,
		State:        t.State,
		GamePlayType: t.GamePlayType,
	}
	for _, v := range t.CurScore {
		res.CurScore = append(res.CurScore, v)
	}
	res.Players = make(map[int32]*tablerecord.TableInfoSamplePlayer)
	for k, v := range t.Players {
		res.Players[k] = v.ToPb()
	}
	return res
}

func (t *TableInfoSamplePlayer) ToPb() *tablerecord.TableInfoSamplePlayer {
	res := &tablerecord.TableInfoSamplePlayer{}
	res.IsReady = t.IsReady
	res.User = t.User.ToPb()

	return res
}

type TableNumCache struct {
	All              int64                                  `bson:"all" json:"all"` //所有的桌子数量
	AllPlayerNums    int64                                  `bson:"all_player_nums" json:"all_player_nums"`
	TableNumCacheMap map[common.TableType]*TableNumCacheOne `bson:"table_num_cache_map" json:"table_num_cache_map"` //各种类型的详细
}

// 某种房间的玩家数量
type TableNumByID struct {
	TableIdNum int64 `bson:"table_id_num" json:"table_id_num"`
	PlayerNums int64 `bson:"player_nums" json:"player_nums"`
	Full       int64 `bson:"full" json:"full"`
	UnFull     int64 `bson:"un_full" json:"un_full"`
}
type TableNumCacheOne struct {
	TableType       common.TableType         `bson:"table_type" json:"table_type"` //房间类型
	TableTypeString string                   `bson:"table_type_string" json:"table_type_string"`
	IDNum           map[string]*TableNumByID `bson:"id_num" json:"id_num"`           //每个id对应的桌子数量和玩家数量
	All             int64                    `bson:"all" json:"all"`                 //所有的数量
	Full            int64                    `bson:"full" json:"sign_t"`             //满房间数量
	UnFull          int64                    `bson:"un_full" json:"un_full"`         //不满房间数量
	PlayerNums      int64                    `bson:"player_nums" json:"player_nums"` //玩家数量
}

// 首席体验官数据
type ExpOfficeData struct {
	Uid      int64  `bson:"uid" json:"uid"`
	Nickname string `bson:"nickname" json:"nickname"`
	Count    int64  `bson:"count" json:"count"`
	Mobile   string `bson:"mobile" json:"mobile"`
}

type WatchPlayer struct {
	UID      int64
	IsOnLine bool
}

// 用户操作
type OpData struct {
	Timestamp int64  `bson:"timestamp" json:"timestamp"`
	Data      string `bson:"data" json:"data"`
}

func (o *OpData) ToPb() *common.OpData {
	return &common.OpData{
		Timestamp: o.Timestamp,
		Data:      o.Data,
	}
}

type MatchType byte

const (
	MatchType_1 MatchType = 1 // 积分赛
	MatchType_2 MatchType = 2 // 淘汰
	MatchType_3 MatchType = 3 // 积分淘汰
)

type EventType byte

const (
	EventType_1 EventType = 1 // 普通
	EventType_2 EventType = 2 // 白卡
	EventType_3 EventType = 3 // vip
	EventType_4 EventType = 4 // 邀请赛
)

type TeamType byte

const (
	TeamType_0 TeamType = 0 // 禁止组队
	TeamType_1 TeamType = 1 // 自行组队
	TeamType_2 TeamType = 2 // 随机组队
)

type ClassType byte

const (
	ClassType_1 ClassType = 1 // 福利赛
	ClassType_2 ClassType = 2 // 线上线下
	ClassType_3 ClassType = 3 // 邀请赛
	ClassType_4 ClassType = 4 // 工会赛
	ClassType_5 ClassType = 5 // 直播
)

type OpenType byte

const (
	OpenType_Count OpenType = 1 // 人满开赛
	OpenType_Time  OpenType = 2 // 按时间开启
)

type LoopType byte

const (
	LoopType_Unknown LoopType = 0
	LoopType_Auto    LoopType = 1 //自动开赛
	LoopType_Custom  LoopType = 2 //自定义开赛时间
)

type CustomSubType byte

const (
	CustomSubType_Once   CustomSubType = 0 //仅开启一次
	CustomSubType_Custom CustomSubType = 1 //自定义
)

type Day int

const (
	Day_1 Day = 1 // 周一
	Day_2 Day = 2 // 周二
	Day_3 Day = 3 // 周三
	Day_4 Day = 4 // 周四
	Day_5 Day = 5 // 周五
	Day_6 Day = 6 // 周六
	Day_7 Day = 0 // 周日
)

type Active byte

const (
	Close Active = 0
	Open  Active = 1
)

type Relive byte

const (
	Relive_Forbidden Relive = 0
	Relive_Allowed   Relive = 1
)

type Delay byte

const (
	Delay_Forbidden Delay = 0
	Delay_Allowed   Delay = 1
)

type RankReward struct {
	Min    int32  `json:"min" bson:"min"` // 最小名次
	Max    int32  `json:"max" bson:"max"` // 最大名次
	Reward []Item `json:"reward" bson:"reward"`
}

type TextReward struct {
	Min    int32    `json:"min" bson:"min"` // 最小名次
	Max    int32    `json:"max" bson:"max"` // 最大名次
	Reward []string `json:"reward" bson:"reward"`
}

type CashReward struct {
	Min    int32 `json:"min" bson:"min"` // 最小名次
	Max    int32 `json:"max" bson:"max"` // 最大名次
	Reward Cash  `json:"reward" bson:"reward"`
}

type Position struct {
	Address      string  `json:"address" bson:"address"`
	Longitude    float64 `json:"longitude" bson:"longitude"` // 经度
	Latitude     float64 `json:"latitude" bson:"latitude"`   // 纬度
	CheckinLimit int32   `json:"checkin_limit"`              // 签到距离限制
}

type MatchChampion struct {
	MatchId   int32      `json:"match_id"`
	MatchName string     `json:"match_name"`
	OpenTime  int64      `json:"open_time"`
	Received  []Item     `json:"received"`
	Champions SimpleUser `json:"champions"`
}
